package com.winchain.provider;

import com.shell.bee.base.utils.StringUtil;
import com.shell.bee.base.utils.SystemUtil;
import com.shell.framework.utils.MessageSender;
import com.shell.framework.utils.ParameterHelper;
import com.shell.framework.utils.SysDateUtil;
import com.shell.governor.modules.message.keyword.BillDctOverdueKeyWord;
import com.shell.governor.modules.vo.ParameterVo;
import com.winchain.chainbill.bill.base.po.CbDct;
import com.winchain.chainbill.bill.base.po.CbDctOverdue;
import com.winchain.chainbill.bill.base.po.CbRec;
import com.winchain.chainbill.bill.base.po.CbSnd;
import com.winchain.chainbill.bill.base.service.CbDctOverdueService;
import com.winchain.chainbill.bill.base.service.CbDctService;
import com.winchain.chainbill.bill.base.service.CbRecService;
import com.winchain.chainbill.bill.base.service.CbSndService;
import com.winchain.chainbill.bill.biz.query.vo.CbDctOverdueVo;
import com.winchain.chainbill.risk.utill.RateUtil;
import com.winchain.chainbill.tbill.base.po.TbDct;
import com.winchain.chainbill.tbill.base.po.TbRec;
import com.winchain.chainbill.tbill.base.po.TbSnd;
import com.winchain.chainbill.tbill.base.service.TbDctService;
import com.winchain.chainbill.tbill.base.service.TbRecService;
import com.winchain.chainbill.tbill.base.service.TbSndService;
import java.math.BigDecimal;
import java.util.List;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class BillDctOverdueProvider {
	private Log logger = LogFactory.getLog(getClass());
	@Autowired
	private CbDctService cbDctService;
	@Autowired
	private CbDctOverdueService cbDctOverdueService;
	@Autowired
	private CbRecService cbRecService;
	@Autowired
	private CbSndService cbSndService;
	@Autowired
	private TbSndService tbSndService;
	@Autowired
	private TbDctService tbDctService;
	@Autowired
	private TbRecService tbRecService;

	@RequestMapping({ "/billDctOverdue/executeOverdueDcts" })
	public void executeOverdueDcts(@RequestParam("wordDate") String wordDate) {
		List<CbDctOverdueVo> list = this.cbDctService.selectDctOverdueRecord(wordDate);
		for (CbDctOverdueVo overdueVo : list) {
			try {
				ParameterVo overdueParam = ParameterHelper.getParameter("6", "OVERDUE_PAY_GRACE_PERIOD",
						overdueVo.getGrpId());
				boolean isOverdue = true;

				int overDay = SysDateUtil.getDaysBetween(overdueVo.getExpDate(), wordDate);
				int graceDay = 1;
				if (overdueParam != null) {
					String value = overdueParam.getParmValue();
					if (!StringUtil.emptyAndNull(value)) {
						int bdays = SysDateUtil.getDaysBetween(overdueVo.getExpDate(), wordDate);
						isOverdue = bdays > Integer.valueOf(value).intValue();
						overDay = bdays - Integer.valueOf(value).intValue();
						graceDay = Integer.valueOf(value).intValue();
					}
				}
				if (isOverdue) {
					CbDctOverdue overdue = getDctOverdueByBizIdAndType(overdueVo.getBizId(), overdueVo.getRpmtType());
					String rateStr = null;
					if ("1".equals(overdueVo.getRpmtType())) {
						rateStr = RateUtil.getFinFixRate("4", "overdue_rate", overdueVo.getFinId(),
								overdueVo.getGrpId());
					} else if ("2".equals(overdueVo.getRpmtType())) {
						rateStr = RateUtil.getFinFixRate("8", "tb_overdue_rate", overdueVo.getFinId(),
								overdueVo.getGrpId());
					}
					if (!StringUtil.emptyAndNull(rateStr)) {
						if (overdue != null) {
							overdue.setOvdInt(calcOverInt(overDay, overdueVo.getDctAmt(), overdue.getOvdRate()));
							this.cbDctOverdueService.updateNotNull(overdue);
						} else {
							overdue = new CbDctOverdue();
							overdue.setOvdId(SystemUtil.getUUID());
							overdue.setBillId(overdueVo.getBillId());
							overdue.setBizId(overdueVo.getBizId());
							overdue.setOvdType(overdueVo.getRpmtType());
							overdue.setOvdDate(SysDateUtil.getPreDay(overdueVo.getExpDate(), graceDay));
							overdue.setCreateTime(SysDateUtil.getSystemDateTime());
							overdue.setOvdRate(new BigDecimal(rateStr));
							overdue.setOvdInt(calcOverInt(overDay, overdueVo.getDctAmt(), new BigDecimal(rateStr)));
							overdue.setOvdState("0");
							this.cbDctOverdueService.save(overdue);
						}
						if ("1".equals(overdueVo.getRpmtType())) {
							CbDct cbDct = (CbDct) this.cbDctService.selectByKey(overdue.getBizId());
							if (cbDct != null) {
								CbRec cbRec = (CbRec) this.cbRecService.selectByKey(cbDct.getBillId());
								if (cbRec != null) {
									CbRec rootRec = (CbRec) this.cbRecService.selectByKey(cbRec.getRootId());
									int level = rootRec.getHldrLvl().intValue();
									if ((rootRec != null) && (StringUtil.emptyAndNull(rootRec.getPrntId()))
											&& (level == 1)) {
										CbSnd cbSnd = this.cbSndService.getBillSndById(rootRec.getBillId());

										sendSmsMessage(cbDct.getSellerNm(),
												SysDateUtil.parseDate(cbDct.getDctDate(), "yyyyMMdd", "yyyy��MM��dd��"),
												cbDct.getDctDays().toString(), cbRec.getBillCode(),
												cbDct.getDctAmt().toString(), "MT09021", cbDct.getFinId());

										sendSmsMessage(cbDct.getSellerNm(),
												SysDateUtil.parseDate(cbDct.getDctDate(), "yyyyMMdd", "yyyy��MM��dd��"),
												cbDct.getDctDays().toString(), cbRec.getBillCode(),
												cbDct.getDctAmt().toString(), "MT09022", cbSnd.getBuyerId());
									}
								}
							}
						} else if ("2".equals(overdueVo.getRpmtType())) {
							TbDct tbDct = (TbDct) this.tbDctService.selectByKey(overdue.getBizId());
							if (tbDct != null) {
								TbSnd tbSnd = this.tbSndService.selectByBillId(tbDct.getBillId());
								if (tbSnd != null) {
									TbRec tbRec = (TbRec) this.tbRecService.selectByKey(tbDct.getBillId());

									sendSmsMessage(tbDct.getSellerNm(),
											SysDateUtil.parseDate(tbDct.getDctDate(), "yyyyMMdd", "yyyy��MM��dd��"),
											tbDct.getDctDays().toString(), tbRec.getBillCode(),
											tbDct.getDctAmt().toString(), "MT09023", tbDct.getFinId());

									sendSmsMessage(tbDct.getSellerNm(),
											SysDateUtil.parseDate(tbDct.getDctDate(), "yyyyMMdd", "yyyy��MM��dd��"),
											tbDct.getDctDays().toString(), tbRec.getBillCode(),
											tbDct.getDctAmt().toString(), "MT09024", tbSnd.getBuyerId());
								}
							}
						}
					}
				}
			} catch (Exception e) {
				this.logger.error("=====BillDctOverdueProvider====", e);
			}
		}
	}

	private CbDctOverdue getDctOverdueByBizIdAndType(String bizId, String ovdType) {
		CbDctOverdue overdue = new CbDctOverdue();
		overdue.setBizId(bizId);
		overdue.setOvdType(ovdType);
		return (CbDctOverdue) this.cbDctOverdueService.selectOne(overdue);
	}

	private BigDecimal calcOverInt(int overDays, BigDecimal dctAmt, BigDecimal rate) {
		return dctAmt.multiply(rate).multiply(new BigDecimal("0.01")).multiply(new BigDecimal(overDays))
				.divide(new BigDecimal("360"), 2, 4);
	}

	private void sendSmsMessage(String sellerName, String applyDate, String dctDays, String billCode, String dctAmt,
			String messageTplId, String entId) {
		try {
			BillDctOverdueKeyWord keyword = new BillDctOverdueKeyWord();
			keyword.setBillCode(billCode);
			keyword.setBillAmt(dctAmt);
			keyword.setApplyDate(applyDate);
			keyword.setDctDays(dctDays);
			keyword.setSellerName(sellerName);
			MessageSender.sendMessageByTmpl("", messageTplId, keyword, entId);
		} catch (Exception e) {
			this.logger.info("===============================" + billCode);
			this.logger.error("BillDctOverdueProvider ������������!", e);
		}
	}
}
